﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;
using Media=Microsoft.Xna.Framework.Media;
using KinectXNATools;
using JupiterLibrary;

namespace KinnectInput.KinectMetro.VideoPlayer
{
    public class KinectMetroVideoPlayer
    {
        public event ClickEventHandler Pushed;

        public event ReleasedEventHandler Release;

        public event ItemAreaEnterHandler EnterArea;

        public event ItemAreaLeaveHandler LeaveArea;

        Point _position;
        public Point Position
        {
            get { return new Point(Parent.BackGroundTarget.X + _position.X, Parent.BackGroundTarget.Y + _position.Y); }
        }
        Rectangle _size;
        public Rectangle Bounds
        {
            get { return new Rectangle(Position.X, Position.Y, _size.Width, _size.Height); }
        }
        public Sprite VideoDisplay { get; private set; }
        Sprite NoVideo;
        public Media.VideoPlayer myPlayer { get; set; }
        public Media.Video movie { get; private set; }
        public VideoSpeechControl speechControl { get; private set; }
        KinectMetroMenu Parent;
        public bool isVisible { get; set; }
        bool _disposingSpeech, speechPlay, speechStop;
        public KinectMetroCardContainer ButtonBar;

        public KinectMetroVideoPlayer(Media.Video movie, Rectangle imageSizeRect, KinectMetroMenu parent, Point position)
        {
            this.myPlayer = new Media.VideoPlayer();
            this.movie = movie;
            _size = imageSizeRect;
            this.Parent = parent;
            this._position = position;
            BuildPlayer(Bounds);
            Rectangle buttonGroupArea = MenuItemSizes.SquareButton;
            //el *2 de separation es porque el card container mueve el button group un separation abajo al dibujarse  
            Vector2 cardContainerPosition = new Vector2(this.Bounds.X, (this.Bounds.Y + this.Bounds.Height));
            //aqui construyo la barra de botones
            Vector2 playPosition = new Vector2(MenuItemSizes.separation, MenuItemSizes.separation);
            Vector2 pausePosition = new Vector2((Bounds.Width/2) - (buttonGroupArea.Width / 2), MenuItemSizes.separation);
            Vector2 stopPosition = new Vector2(Bounds.Width - buttonGroupArea.Width - MenuItemSizes.separation, MenuItemSizes.separation);
            
            KinectMetroButtonGrp playGroup = new KinectMetroButtonGrp(buttonGroupArea, playPosition, this.Parent.GraphicsDevice);
            
            KinectMetroButtonGrp pauseGroup = new KinectMetroButtonGrp(buttonGroupArea, pausePosition, this.Parent.GraphicsDevice);
            
            KinectMetroButtonGrp stopGroup = new KinectMetroButtonGrp(buttonGroupArea, stopPosition, this.Parent.GraphicsDevice);
            ButtonBar = new KinectMetroCardContainer(cardContainerPosition, new KinectMetroButtonGrp[] { playGroup, pauseGroup, stopGroup });
            ButtonBar.ButtonGroups[0].BuildGroup(ButtonBar, parent.Containers[0].ButtonGroups[0].backGroundText.Texture);
            

            playGroup.addButton(new KinectMetroIconButton(Vector2.Zero, MenuItemSizes.SquareButton, MenuStyle.ButtonBackGround, Jupiter.Content.Load<Microsoft.Xna.Framework.Graphics.Texture2D>("Video/Play")));
            
            playGroup.Buttons[0].Build(playGroup);
            playGroup.BuildGroup(this.ButtonBar);
            playGroup.Update();
            pauseGroup.addButton(new KinectMetroIconButton(Vector2.Zero, MenuItemSizes.SquareButton, MenuStyle.ButtonBackGround, Jupiter.Content.Load<Microsoft.Xna.Framework.Graphics.Texture2D>("Video/Pause")));
            
            pauseGroup.Buttons[0].Build(pauseGroup);
            pauseGroup.BuildGroup(this.ButtonBar);
            pauseGroup.Update();
            KinectMetroIconButton stopButton = new KinectMetroIconButton(Vector2.Zero, MenuItemSizes.SquareButton, MenuStyle.ButtonBackGround, Jupiter.Content.Load<Microsoft.Xna.Framework.Graphics.Texture2D>("Video/Stop"));
            
            stopGroup.addButton(stopButton);
            stopGroup.Buttons[0].Build(stopGroup);
            stopGroup.BuildGroup(this.ButtonBar);
            stopGroup.Update();
        }
        private void BuildPlayer(Rectangle imageSizeRect)
        {
            VideoDisplay = new Sprite();
            VideoDisplay.SetRectangle(imageSizeRect);
            NoVideo = new Sprite();
            NoVideo.SetRectangle(imageSizeRect);
            NoVideo.SetColor(new Color(0, 0, 0.25f, 0.9f));
            NoVideo.Update();
        }
        void speechControl_StopTold(object sender, EventArgs e)
        {
            myPlayer.Stop();
        }

        void speechControl_PlayTold(object sender, EventArgs e)
        {
            myPlayer.Play(movie);
        }
        public void Update()
        {
            
            if (isVisible)
            {
                if (myPlayer != null && movie != null && myPlayer.State == Media.MediaState.Playing)
                {
                    VideoDisplay.Texture = myPlayer.GetTexture();
                }
                if (speechControl == null)
                {
                    speechControl = new VideoSpeechControl();
                    speechControl.PlayTold += new EventHandler(speechControl_PlayTold);
                    speechControl.StopTold += new EventHandler(speechControl_StopTold);
                    speechControl.SpeechRecognized += new EventHandler(speechControl_SpeechRecognized);
                    speechControl.Start();
                }
                this.ButtonBar.Update();
            }
            else if (Parent.MenuState == KinectMetroMenuState.Colapsed)
            {
                if (speechControl != null && !_disposingSpeech)
                {
                    kill_speechControll();
                }
                myPlayer.Stop();
            }
            else
            {

                if (speechControl != null && !_disposingSpeech)
                {
                    kill_speechControll();
                }
                myPlayer.Stop();
            }
            VideoDisplay.Update();
        }
        public void kill_speechControll()
        {
            if (speechControl != null && !_disposingSpeech)
            {
                _disposingSpeech = true;

                System.Threading.ThreadPool.QueueUserWorkItem((o) =>
                {
                    try
                    {
                        if (speechControl != null)
                        {
                            speechControl.Stop();
                            speechControl.Dispose();
                            speechControl = null;
                        }
                    }
                    finally
                    {
                        _disposingSpeech = false;
                    }
                });
            }
            myPlayer.Stop();
        }

        void speechControl_SpeechRecognized(object sender, EventArgs e)
        {
            if (!KinectXNATools.MediaEvalulator.isPlaying(JupiterLibrary.Jupiter.soundPing.State))
            {
                JupiterLibrary.Jupiter.soundPing.Play();
            }
        }

        public void Draw()
        {
            if (isVisible)
            {

                if (myPlayer.State == Media.MediaState.Stopped)
                {
                    NoVideo.Draw();
                }
                else
                {
                    if (myPlayer.State == Media.MediaState.Playing || myPlayer.State == Media.MediaState.Paused)
                    {
                        VideoDisplay.Draw();
                    }
                    else
                        NoVideo.Draw();
                }
                ButtonBar.Draw();
            }
        }
    }
}
